﻿///////////////////////////////////////////////////////////////////////////////
// File:        EchoServer.cc
// Author:      671643387@qq.com
// Description:
///////////////////////////////////////////////////////////////////////////////

#include <stdio.h>
#include <boost/bind.hpp>
#include "EchoServer.hpp"
using namespace nio::net;

#define BUFFER_SIZE 0x4000

EchoServer::EchoServer()
: server_()
{
    server_.setConnectionEstablishedFN(
        boost::bind(&EchoServer::onConnectionEstablised, this, _1));

    server_.setConnectionReabledFN(
        boost::bind(&EchoServer::onConnectionReadable, this, _1, _2));
    server_.setConnectionWritableFN(
        boost::bind(&EchoServer::onConnectionWritable, this, _1, _2));
    server_.setConnectionErrorFN(
        boost::bind(&EchoServer::onConnectionError, this, _1));
    server_.setConnectionHeartbeatFN(
        boost::bind(&EchoServer::onConnectionHeartbeat, this, _1));
    server_.setConnectionCloseFN(
        boost::bind(&EchoServer::onConnectionClose, this, _1));
}

EchoServer::~EchoServer()
{

}

bool EchoServer::open(std::string addr, int port, int backlog, int threads
    , bool useBuffSet, unsigned int sndBufSize, unsigned int rcvBufSize
    , unsigned int isSize, unsigned int osSize)
{
    server_.config_Threads(threads);
    server_.config_ServerFrameTime(0);
    server_.config_ThreadFrameTime(0);
    server_.config_UseSockBuffSizeSet(useBuffSet);
    server_.config_ConnectionSendBuffSize(sndBufSize);
    server_.config_ConnectionRecvBuffSize(rcvBufSize);
    server_.config_ConnectionInputStreamSize(isSize);
    server_.config_ConnectionOutputStreamSize(osSize);
    return server_.open(addr, port, backlog);
}

void EchoServer::close()
{
    dumpStatics();
    server_.close();
}

void EchoServer::run()
{
    dumpConfig();
    server_.run();
}

void EchoServer::onConnectionEstablised(nio::net::ConnectionPtr& conn)
{

}

void EchoServer::onConnectionReadable(nio::net::Connection& conn, nio::net::ConnectionInputStream& is)
{
    char buff[0x4000];
    unsigned int bytsRead = is.read(buff, sizeof(buff));
    if (bytsRead > 0)
    {
        conn.getOutputStream().write(buff, bytsRead);
    }
}

void EchoServer::onConnectionWritable(nio::net::Connection& conn, nio::net::ConnectionOutputStream& os)
{
    
}

void EchoServer::onConnectionError(nio::net::Connection& conn)
{

}

void EchoServer::onConnectionHeartbeat(nio::net::Connection& conn)
{

}

void EchoServer::onConnectionClose(nio::net::Connection& conn)
{

}

void EchoServer::dumpConfig()
{
    nio::net::Server::Config config;
    server_.getConfig(config);

    printf("-- dumpConfig\n");
    printf("threads                             :    %d\n", config.threads);
    printf("threadFrameTime                     :    %ld\n", config.threadFrameTime);
    printf("serverFrameTime                     :    %ld\n", config.serverFrameTime);
    printf("connectionHeartbeatTime             :    %ld\n", config.connectionHeartbeatTime);
    printf("useSockBuffSet                      :    %d\n", config.useSockBuffSet);
    printf("sndBuffSize                         :    %d\n", config.sndBuffSize);
    printf("rcvBuffSize                         :    %d\n", config.rcvBuffSize);
    printf("connectionInputStreamSize           :    %d\n", config.connectionInputStreamSize);
    printf("connectionOutputStreamSize          :    %d\n", config.connectionOutputStreamSize);
    printf("connectionUserIO                    :    %d\n", config.connectionUserIO);
#if defined(__LINUX__)
    printf("epollET                             :    %d\n", config.epollET);
#endif

    printf("\n");
}

void EchoServer::dumpStatics()
{
    nio::net::Server::Statics statics;
    server_.getStatics(statics);

    printf("-- dumpStatics\n");
    printf("state                               :    %d\n", statics.state);
    printf("connIdGen                           :    %d\n", statics.connIdGen);
    printf("connLoad                            :    %d\n", statics.connLoad);
    printf("connTotal                           :    %d\n", statics.connTotal);
    printf("frameUseTime                        :    %ld\n", statics.frameUseTime);
    printf("bytsSend                            :    %lld\n", statics.bytsSend);
    printf("bytsRecv                            :    %lld\n", statics.bytsRecv);

    for (std::vector<nio::net::ServerThread>::size_type x = 0;
        x < statics.threadsStatics.size(); ++x)
    {
        printf("%ld ---->\n", x);
        printf("connLoad                            :    %d\n", statics.threadsStatics[x].connLoad);
        printf("frameUseTime                        :    %ld\n", statics.threadsStatics[x].frameUseTime);
    }

    printf("\n");
}